pub(crate) struct VolumeEnvelope {
    period: u8,
    goes_up: bool,
    delay: u8,

    initial_volume: u8,
    pub(crate) volume: u8,
}

impl VolumeEnvelope {
    pub(crate) fn new() -> Self {
        Self {
            period: 0,
            goes_up: false,
            delay: 0,

            initial_volume: 0,
            volume: 0,
        }
    }

    pub(crate) fn rb(&self, addr: u16) -> u8 {
        match addr {
            0xFF12 | 0xFF17 | 0xFF21 => {
                let tmp1 = (self.initial_volume & 0xF) << 4;

                let tmp2 = if self.goes_up { 0x08 } else { 0 };

                let tmp3 = self.period & 0x7;

                tmp1 | tmp2 | tmp3
            }

            _ => unimplemented!("Not impl yet"),
        }
    }

    pub(crate) fn wb(&mut self, addr: u16, value: u8) {
        match addr {
            0xFF12 | 0xFF17 | 0xFF21 => {
                self.period = value & 0x7;
                self.goes_up = value & 0x08 == 0x08;
                self.initial_volume = value >> 4;
                self.volume = self.initial_volume;
            }
            0xFF14 | 0xFF19 | 0xFF23 if value & 0x80 == 0x80 => {
                self.delay = self.period;
                self.volume = self.initial_volume;
            }

            _ => (),
        }
    }

    pub(crate) fn step(&mut self) {
        if self.delay > 1 {
            self.delay -= 1;
        } else if self.delay == 1 {
            self.delay = self.period;
            if self.goes_up && self.volume < 15 {
                self.volume += 1;
            } else if !self.goes_up && self.volume > 0 {
                self.volume -= 1;
            }
        }
    }
}

// DONE
